package com.zisu.springcloud.controller;

import com.netflix.hystrix.contrib.javanica.annotation.DefaultProperties;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixProperty;
import com.zisu.springcloud.service.PaymentHystrixService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;

/**
 * @Author: 蔡翔
 * @Date: 2020/9/5 15:24
 * @Version 1.0
 */
@RestController
@Slf4j
//引入这个注解 是为了不 一一指定 服务降级方法，因为一个服务指定一个降级会非常麻烦。。（这个controller中没有指定特定的降级方法那么就用这个公用的降级方法）
//注意 Hystrix 不同模式混用 可能会存在一些问题
@DefaultProperties(defaultFallback = "globalPaymentTimeOutFallbackMethod")
public class OrderHystrixController {
    @Resource
    private PaymentHystrixService paymentHystrixService;

    @Value("${server.port}")
    private String serverPort;

    @GetMapping("/consumer/payment/hystrix/ok/{id}")
    public String paymentInfo_OK(@PathVariable("id") Integer id){
        String result = paymentHystrixService.paymentInfo_OK(id);
        log.info("*******result:"+result);
        return result;
    }
//
//    @GetMapping("/consumer/payment/hystrix/timeout/{id}")
//    public String paymentInfo_TimeOut(@PathVariable("id") Integer id){
//        String result = paymentHystrixService.paymentInfo_TimeOut(id);
//        log.info("*******result:"+result);
//        return result;
//    }
    //1.controller层的 @DefaultProperties(defaultFallback = "globalPaymentTimeOutFallbackMethod") 配合使用
    // 注意要用何种方法 那么 yml中必须加入#feign:
                                    //#  hystrix:
                                    //#    enabled: true
    //其他方式 yml 中不能加feign...
    @GetMapping("/consumer/payment/hystrix/timeout3/{id}")
    //@HystrixCommand 没有这个注解的话  就代表这个接口不进行服务降级
    @HystrixCommand
    public String paymentInfo_TimeOut3(@PathVariable("id") Integer id){
        String result = paymentHystrixService.paymentInfo_TimeOut(id);
        return result;
    }

    //写在service层（源头层）@FeignClient(value = "CLOUD-PROVIDER-HYSTRIX-PAYMENT",fallback = PaymentFallBackServiceImpl.class) 配合使用
    @GetMapping("/consumer/payment/hystrix/timeout4/{id}")
    public String paymentInfo_TimeOut4(@PathVariable("id") Integer id){
        String result = paymentHystrixService.paymentInfo_TimeOut(id);
        return result;
    }


    //3.单独使用 一个方法 指定一个 fallback方法。
    //一般服务 降级 是放在客户端（服务调用方）那里的 ，，但是也可以放在服务提供方那里
    @GetMapping("/consumer/payment/hystrix/timeout/{id}")
    @HystrixCommand(fallbackMethod = "paymentTimeOutFallbackMethod",commandProperties = {
            @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds",value = "5500")  //3秒钟以内就是正常的业务逻辑
    })
    public String paymentInfo_TimeOut2(@PathVariable("id") Integer id){
        String result = paymentHystrixService.paymentInfo_TimeOut(id);
        return result;
    }

    //兜底方法
    public String paymentTimeOutFallbackMethod(@PathVariable("id") Integer id){
        return "我是消费者80，对付支付系统繁忙请10秒钟后再试或者自己运行出错请检查自己,(┬＿┬)";
    }

    //全局的 fallback 兜底方法
    public String globalPaymentTimeOutFallbackMethod(){
        return "（全局）我是消费者80，对付支付系统繁忙请10秒钟后再试或者自己运行出错请检查自己,(┬＿┬)";
    }

}
